package domain;

import java.util.ArrayList;
import java.util.List;

import org.lightcouch.CouchDbClient;
import org.lightcouch.DocumentConflictException;
import org.lightcouch.NoDocumentException;

import documents.DocPublicacion;
import documents.DocUsuario;

public class UsuarioDAO {
	
	private static final CouchDbClient dbClient = new CouchDbClient();
	
	public static Usuario entrarCon(Usuario usuario){
		DocUsuario user = new DocUsuario(usuario);
		
		if((user.getId() == null) && uniqueUser(user)) {
			System.out.println("Usuario ha sido registrado satisfactoriamente: "+ user.getUsername());
			user.setId(user.getUsername());
			dbClient.save(user);
		} else {
			System.out.println("Nombre de usuario no disponible");
		}
		
		return dbClient.find(Usuario.class, usuario.getUsername());
	}
	
	public static void publicar(Publicacion publicacion) {
		DocPublicacion p = new DocPublicacion(publicacion);
		
		if(notExistsPublicacion(p)) {
			System.out.println("La publicacion ha sido subida con el id: "+ p.getId());
			updateUser(publicacion);
			dbClient.save(p);
		} else {
			System.out.println("Ya existe una publicacion con este nombre");
		}
	}
	
	private static void updateUser(Publicacion publicacion) {
		try {
			DocUsuario p = dbClient.find(DocUsuario.class, publicacion.getUsuario().getUsername());
			p.getPublicaciones().add(publicacion);

			dbClient.update(p);
			
		} catch(DocumentConflictException e) {
			System.out.println("No se puede actualizar la publicacion nueva del usuario");
		} catch(NoDocumentException e){
			System.out.println("Ya no existe el usuario");
		}
		
	}

	// Se ofeta una publicacion y se actualiza en la base
	public static void ofertar(Usuario user, Publicacion publicacion) {
		try {
			DocPublicacion p = dbClient.find(DocPublicacion.class, publicacion.generateId());
			
			Publicacion actualizada;
			
			if(p.isSubasta()) {
				actualizada = new Subasta(p);
			} else {
				actualizada = new VentaDirecta(p);
			}
			
			actualizada.ofertar(user);
			p.update(actualizada);
			
			dbClient.update(p);
			
			String operacion = p.isSubasta() ? "ofertada" : "comprada";
			System.out.println(p.getNombre()+" publicado por "+publicacion.getUsuario()+" ha sido "+operacion+" por "+user.getUsername()+" al precio de "+actualizada.getPrecio());

		} catch(DocumentConflictException e) {
			System.out.println("No se puede actualizar su oferta");
		} catch(NoDocumentException e){
			System.out.println("La publicacion ya no se encuentra disponible para ofertar");
		}
	}

	// Devuelve la lista de publicaciones para el usuario dado
	public static List<Publicacion> getPublicaciones(Usuario foo) {
		List<Publicacion> result = new ArrayList<Publicacion>();
		
		try {
			result = dbClient.find(DocUsuario.class, foo.getUsername()).getPublicaciones();
		} catch(NoDocumentException e){
			System.out.println("La publicacion ya no se encuentra disponible para ofertar");
		}
		
		return result;
	}
	
	
	
	
	
	
	private static boolean notExistsPublicacion(DocPublicacion elem) {
		try {
			dbClient.find(elem.getClass(), elem.generateId());
			return false;
		} catch(NoDocumentException e) {
			return true;			
		}
	}
	
	private static boolean uniqueUser(DocUsuario elem) {
		try {
			dbClient.find(elem.getClass(), elem.getUsername());
			return false;
		} catch(NoDocumentException e) {
			return true;			
		}
	}
}
